/*
 * MultirootSolver.h
 *
 *  Created on: 23 Jun 2011
 *      Author: allan
 */

#ifndef MULTIROOTSOLVER_H_
#define MULTIROOTSOLVER_H_

// Eigen includes
#include <Eigen/Dense>
using namespace Eigen;

class MultirootProblem
{
public:
	MultirootProblem() {}
	
	virtual ~MultirootProblem() {}
	
	virtual void Function(const VectorXd& x, VectorXd& F) = 0;
	
	virtual void Jacobian(const VectorXd& x, MatrixXd& J) = 0;
	
	virtual void FunctionJacobian(const VectorXd& x, VectorXd& F, MatrixXd& J) { Function(x, F); Jacobian(x, J); }
	
	virtual void PostProcess(VectorXd& x) {}
};

enum MultirootSolverType
{
	// for more information, check: http://www.gnu.org/software/gsl/manual/html_node/Algorithms-using-Derivatives.html
	MULTIROOTSOLVER_HYBRIDSJ,
	MULTIROOTSOLVER_HYBRIDJ,
	MULTIROOTSOLVER_NEWTON,
	MULTIROOTSOLVER_GNEWTON
};

class MultirootSolver
{
public:
	MultirootSolver();
	
	void
	SetSolverType(MultirootSolverType type);
	
	void
	SetSolverOptions(double tolerance, unsigned maxiterations);
	
	bool
	Solve(MultirootProblem& nonlinearProblem, VectorXd& x);
	
private:
	MultirootSolverType type;
	
	double tolerance;

	unsigned maxiterations;
};

#endif /* MULTIROOTSOLVER_H_ */
